package com.sky.service.admin.impl;

import com.github.pagehelper.Page;
import com.github.pagehelper.PageHelper;
import com.sky.dto.SetmealDTO;
import com.sky.dto.SetmealPageQueryDTO;
import com.sky.exception.ParamsIllegalException;
import com.sky.exception.SetmealExitsException;
import com.sky.mapper.admin.SetmealDishMapper;
import com.sky.mapper.admin.SetmealMapper;
import com.sky.pojo.Setmeal;
import com.sky.pojo.SetmealDish;
import com.sky.result.PageResult;
import com.sky.result.Result;
import com.sky.service.admin.SetmealService;
import com.sky.vo.SetmealVO;
import lombok.RequiredArgsConstructor;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Collections;
import java.util.List;
import java.util.Objects;

/**
 * 套餐管理业务实现类
 *
 * @Author: Zhy
 * @Date: 2025-01-21 下午6:39
 * @Version: 1.0
 */
@Service
@RequiredArgsConstructor
public class SetmealServiceImpl implements SetmealService {

	private final SetmealMapper setmealMapper;
	private final SetmealDishMapper setmealDishMapper;

	/**
	 * 新增套餐
	 *
	 * @return:
	 * @param:
	 */
	@Override
	@Transactional(rollbackFor = Exception.class)
	public Result<String> addSetmeal(SetmealDTO setmealDTO) {
		// 参数校验
		if (Objects.isNull(setmealDTO) ||
			Objects.isNull(setmealDTO.getName()) ||
			Objects.isNull(setmealDTO.getPrice()) ||
			Objects.isNull(setmealDTO.getImage()) ||
			Objects.isNull(setmealDTO.getCategoryId()) ||
			Objects.isNull(setmealDTO.getSetmealDishes())) {
			throw new ParamsIllegalException("新增套餐出错了，请稍后重试！");
		}

		// 业务逻辑处理
		// 1. 判断是否存在相同名称的套餐
		Long count = setmealMapper.countByName(setmealDTO);
		if (count > 0) {
			throw new SetmealExitsException("套餐名称已存在，请重新输入！");
		}
		// 2. 保存套餐信息
		Setmeal setmeal = new Setmeal();
		BeanUtils.copyProperties(setmealDTO, setmeal);
		setmealMapper.insertSelective(setmeal);
		// 3. 保存套餐菜品信息
		List<SetmealDish> setmealDishes = setmealDTO.getSetmealDishes();
		setmealDishes.forEach(setmealDish -> setmealDish.setSetmealId(setmeal.getId()));
		setmealDishMapper.insertDishList(setmealDishes);

		// 返回结果
		return Result.success("新增套餐成功！");
	}

	/**
	 * 分页查询套餐
	 *
	 * @return:
	 * @param:
	 */
	@Override
	public Result<PageResult<Setmeal>> pageQuerySetmeal(SetmealPageQueryDTO setmealPageQueryDTO) {
		// 参数校验

		// 业务逻辑处理
		// 开启分页查询
		PageHelper.startPage(setmealPageQueryDTO.getPage(), setmealPageQueryDTO.getPageSize());
		// 查询套餐信息
		List<Setmeal> pageResult = setmealMapper.pageQuerySetmeal(setmealPageQueryDTO);
		Page<Setmeal> page = (Page<Setmeal>) pageResult;

		return Result.success(new PageResult<>(page.getTotal(), page.getResult()));
	}

	/**
	 * 根据 id 查询套餐
	 *
	 * @return:
	 * @param:
	 */
	@Override
	@Transactional(rollbackFor = Exception.class)
	public Result<SetmealVO> getSetmealById(Long setmealId) {
		// 参数校验
		if (Objects.isNull(setmealId)) {
			throw new ParamsIllegalException("查询套餐出错了，请稍后重试！");
		}

		// 业务逻辑处理
		// 1. 查询套餐信息
		Setmeal setmeal = setmealMapper.selectSetmealById(setmealId);
		// 2. 查询套餐菜品信息
		List<SetmealDish> setmealDishes = setmealDishMapper.selectBySetmealId(setmealId);
		// 3. 组装结果
		SetmealVO setmealVO = new SetmealVO();
		BeanUtils.copyProperties(setmeal, setmealVO);
		setmealVO.setSetmealDishes(setmealDishes);

		return Result.success(setmealVO);
	}

	/**
	 * 更新套餐数据
	 *
	 * @return:
	 * @param:
	 */
	@Override
	@Transactional(rollbackFor = Exception.class)
	public Result<String> updateSetmeal(SetmealDTO setmealDTO) {
		// 参数校验
		if (Objects.isNull(setmealDTO) ||
			Objects.isNull(setmealDTO.getName()) ||
			Objects.isNull(setmealDTO.getPrice()) ||
			Objects.isNull(setmealDTO.getImage()) ||
			Objects.isNull(setmealDTO.getCategoryId()) ||
			Objects.isNull(setmealDTO.getSetmealDishes())) {
			throw new ParamsIllegalException("更新套餐出错了，请稍后重试！");
		}

		// 业务逻辑处理
		// 1. 判断是否存在相同名称的套餐
		Long count = setmealMapper.countByName(setmealDTO);
		if (count > 0) {
			throw new SetmealExitsException("套餐名称已存在，请重新输入！");
		}
		// 2. 更新套餐信息
		Setmeal setmeal = new Setmeal();
		BeanUtils.copyProperties(setmealDTO, setmeal);
		setmealMapper.updateSetmealById(setmeal);
		// 3. 更新套餐菜品信息（先删再加）
		setmealDishMapper.deleteBySetmealIds(Collections.singletonList(setmeal.getId()));
		List<SetmealDish> setmealDishes = setmealDTO.getSetmealDishes();
		setmealDishes.forEach(setmealDish -> setmealDish.setSetmealId(setmeal.getId()));
		setmealDishMapper.insertDishList(setmealDishes);

		return Result.success("更新套餐成功！");
	}

	/**
	 * 更新套餐状态
	 *
	 * @return:
	 * @param:
	 */
	@Override
	public Result<String> updateSetmealStatus(Integer status, Long id) {
		// 参数校验
		if (Objects.isNull(status) || Objects.isNull(id)) {
			throw new ParamsIllegalException("更新套餐状态出错了，请稍后重试！");
		}

		// 业务逻辑处理
		setmealMapper.updateSetmealStatus(status, id);

		return Result.success("更新套餐状态成功！");
	}

	/**
	 * 批量删除套餐
	 *
	 * @return:
	 * @param:
	 */
	@Override
	@Transactional(rollbackFor = Exception.class)
	public Result<String> deleteSetmealByIds(List<Long> ids) {
		// 参数校验
		if (Objects.isNull(ids) || ids.isEmpty()) {
			throw new ParamsIllegalException("删除套餐出错了，请稍后重试！");
		}

		// 业务逻辑处理
		setmealMapper.deleteSetmealByIds(ids);
		setmealDishMapper.deleteBySetmealIds(ids);

		return Result.success("删除套餐成功！");
	}

}
